package com.matchmaking.auth.controller;

import cn.hutool.captcha.CaptchaUtil;
import cn.hutool.captcha.ShearCaptcha;
import cn.hutool.captcha.generator.MathGenerator;
import cn.hutool.core.lang.Console;
import cn.hutool.core.lang.tree.Tree;
import cn.hutool.core.lang.tree.TreeNodeConfig;
import cn.hutool.core.lang.tree.TreeUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.crypto.digest.DigestUtil;
import cn.hutool.jwt.JWT;
import cn.hutool.jwt.signers.JWTSignerUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.matchmaking.auth.config.R;
import com.matchmaking.auth.domain.LoginForm;
import com.matchmaking.auth.domain.SysMenu;
import com.matchmaking.auth.domain.SysUser;
import com.matchmaking.auth.domain.SysUserRole;
import com.matchmaking.auth.service.SysMenuService;
import com.matchmaking.auth.service.SysUserRoleService;
import com.matchmaking.auth.service.SysUserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.HashMap;
import java.util.List;
import java.util.concurrent.TimeUnit;

/**
 * @Description: TODO
 * @Author 卟哭！
 * @Date 2024/03/23  11:34
 * @Version 1.0
 */
@RestController
@RequestMapping("auth")
public class AuthController {
    @Autowired
    private SysUserService sysUserService;
    @Autowired
    private RedisTemplate<String, String> redisTemplate;
    @Autowired
    private SysUserRoleService userRoleService;
    @Autowired
    private HttpServletResponse response;
    @Autowired
    private SysMenuService sysMenuService;


    @GetMapping("code")
    public void code( String uuid) throws IOException {
        //定义图形验证码的长、宽、验证码字符数、干扰线宽度
        ShearCaptcha captcha = CaptchaUtil.createShearCaptcha(200, 45, 4, 4);
        captcha.setGenerator(new MathGenerator(1));
        // 重新生成code
        captcha.createCode();
        Console.log(captcha.getCode());
        //验证图形验证码的有效性，返回boolean值
        captcha.verify("1234");
        //验证码通过流发送浏览器
        captcha.write(response.getOutputStream());
        //验证码保存到redis 时长五分钟
        redisTemplate.opsForValue().set(uuid, captcha.getCode(), 5, TimeUnit.MINUTES);
        //验证码  重复点击校验 10秒内只能点击一次
        redisTemplate.opsForValue().set(uuid + "limit", captcha.getCode(), 10, TimeUnit.SECONDS);
    }

    //点击更换验证码
    @GetMapping("checkCode")
    public R checkCode(String uuid) {
        //判断redis中是否存在该校验
        Boolean b = redisTemplate.hasKey(uuid + "limit");
        return R.successed(b);
    }

    @PostMapping("login")
    public R login(@RequestBody  LoginForm loginForm) {
        if (!redisTemplate.hasKey(loginForm.getUuid())) {
            return R.failed("验证码已经过期");

        }
        String codes = redisTemplate.opsForValue().get(loginForm.getUuid()) + "";
        boolean verify = new MathGenerator().verify(codes, loginForm.getCode());
        System.err.println("验证码校验:"+verify);
        if (!verify) {
            return R.failed("验证码输入有误！！");
        }
        QueryWrapper<SysUser> sysUserQueryWrapper = new QueryWrapper<>();
        if (StrUtil.isNotEmpty(loginForm.getUsername())) {

            sysUserQueryWrapper.eq("user_name", loginForm.getUsername());
        } else {
            sysUserQueryWrapper.eq("phonenumber", loginForm.getPhonnenumber());
        }
        SysUser one = sysUserService.getOne(sysUserQueryWrapper);
        if (one == null) {
            return R.failed("用户不存在");
        }
        String password = DigestUtil.md5Hex(loginForm.getPassword());
        if (!StrUtil.equalsIgnoreCase(one.getPassword(), password)) {
            return R.failed("密码错误");
        }
        QueryWrapper<SysUserRole> sysUserRoleQueryWrapper = new QueryWrapper<>();
        sysUserRoleQueryWrapper.eq("user_id", one.getUserId());
        List<SysUserRole> roleList = userRoleService.list(sysUserRoleQueryWrapper);
        //生成不签名 jwt token
        String token = JWT.create()
                .setPayload("user_id", one.getUserId())
                .setPayload("user_name", one.getUserName())
                .setPayload("roleList", roleList)
                .setSigner(JWTSignerUtil.none())
                .sign();
        HashMap<String, Object> map = new HashMap<String, Object>();
        //根据用户id查询菜单
        List<SysMenu> list = sysMenuService.selectMenusByUserId(one.getUserId());
        //把用户的菜单封装成树状结构
        //配置
        TreeNodeConfig treeNodeConfig = new TreeNodeConfig();
// 自定义属性名 都要默认值的
        treeNodeConfig.setIdKey("menuId");
        treeNodeConfig.setNameKey("menuName");

//转换器
        List<Tree<String>> treeNodes = TreeUtil.build(list, "0", treeNodeConfig,
                (treeNode, tree) -> {
                    tree.setId(treeNode.getMenuId()+"");
                    tree.setParentId(treeNode.getParentId()+"");
                    tree.setName(treeNode.getMenuName());
                    // 扩展属性 ...
                    tree.putExtra("path", treeNode.getPath());
                    tree.putExtra("component", treeNode.getComponent());
                    tree.putExtra("perms", (treeNode.getPerms()));
                    //      菜单类型（M目录 C菜单 F按钮）
                    tree.putExtra("menuType", treeNode.getMenuType());
                });


        map.put("token", token);
        map.put("userId", one.getUserId());
        map.put("menus", treeNodes);
        //登录成功 销毁验证码
        redisTemplate.delete(loginForm.getUuid());
        return R.successed(map);
    }


}
